/**
 * @File:ring_buffer_example.c
 * @Version:V1.0
 * @Author:rudius
 * @Brief:
 * @Logs:
 * 	Date		Author		Notes
 * 	2025-06-17	rudius		first version
 */

// <<< Use Configuration Wizard in Context Menu >>>

/* Private includes --------------------------------------------------------- */
#include "ring_buffer.h"
#include <rtthread.h>
#include <string.h>

#ifdef __cplusplus
extern "C"
{
#endif

/* Private config ----------------------------------------------------------- */
#define TEST_BUFFER_SIZE 32
#define THREAD_STACK_SIZE 1024
#define THREAD_PRIORITY 20
#define THREAD_TIMESLICE 10
uint8_t producer_buffer[TEST_BUFFER_SIZE];
uint8_t consumer_buffer[TEST_BUFFER_SIZE];
/* Private defines ---------------------------------------------------------- */
/* Private typedef ---------------------------------------------------------- */
/* Private variables -------------------------------------------------------- */
/* 测试数据序列 */
static const uint8_t test_data[TEST_BUFFER_SIZE] =
{
	0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,
	0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F,
	0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17,
	0x18, 0x19, 0x1A, 0x1B, 0x1C, 0x1D, 0x1E, 0x1F
};
/* Private function prototypes ---------------------------------------------- */

/*----------------------------------------------------------------------------*/
/* Private functions -------------------------------------------------------- */

/* 测试结果报告 */
static void report_test(const char* name, rt_bool_t passed)
{
	rt_kprintf("[%s] %s - %s\n",
	           passed ? "PASS" : "FAIL",
	           name,
	           passed ? "Succeeded" : "Failed");
}

/* 基本功能测试 */
static void ring_buf_basic_test(void)
{
	rt_kprintf("\n=== Ring Buffer Basic Test ===\n");
	ring_buf_t rb;
	uint8_t buffer[TEST_BUFFER_SIZE];
	rt_size_t write_size, read_size;

	// 初始化缓冲区
	RT_ASSERT(ring_buf_init(&rb, TEST_BUFFER_SIZE) == RT_EOK);

	// 测试1: 空缓冲区状态
	rt_bool_t result = ring_buf_is_empty(&rb);
	report_test("Initial Empty", result);

	// 测试2: 写入少于容量
	write_size = ring_buf_put(&rb, test_data, 8);
	report_test("Partial Write", write_size == 8);

	// 测试3: 数据量检查
	rt_size_t data_size = ring_buf_data_size(&rb);
	report_test("Data Size", data_size == 8);

	// 测试4: 部分读取
	read_size = ring_buf_get(&rb, buffer, 4);
	report_test("Partial Read",
	            read_size == 4 &&
	            memcmp(buffer, test_data, 4) == 0);

	// 测试5: 剩余数据量
	data_size = ring_buf_data_size(&rb);
	report_test("Remaining Data", data_size == 4);

	// 测试6: 完全填充
	rt_size_t remaining = TEST_BUFFER_SIZE - data_size;
	write_size = ring_buf_put(&rb, test_data + data_size, remaining);
	report_test("Fill Buffer",
	            write_size == remaining &&
	            ring_buf_is_full(&rb));

	// 测试7: 满状态检查
	result = ring_buf_is_full(&rb);
	report_test("Full Check", result);

	// 测试8: 空读取返回0
	uint8_t temp;
	read_size = ring_buf_get(&rb, &temp, 0);
	report_test("Zero Read", read_size == 0);

	// 测试9: 覆盖写入
	const uint8_t overflow_data[8] = {0xFF, 0xEE, 0xDD, 0xCC, 0xBB, 0xAA, 0x99, 0x88};
	write_size = ring_buf_put(&rb, overflow_data, sizeof(overflow_data));
	report_test("Overflow Write",
	            write_size == sizeof(overflow_data) &&
	            ring_buf_is_full(&rb));

	// 测试10: 正确覆盖
	// 先读取未覆盖部分的数据
    rt_size_t unoverwritten_size = TEST_BUFFER_SIZE - sizeof(overflow_data);
    read_size = ring_buf_get(&rb, buffer, unoverwritten_size);
    
    // 然后读取覆盖写入的数据
    read_size = ring_buf_get(&rb, buffer, sizeof(overflow_data));
    report_test("Overflow Read",
                read_size == sizeof(overflow_data) &&
                    memcmp(buffer, overflow_data, sizeof(overflow_data)) == 0);

	// 测试11: 重置功能
	ring_buf_reset(&rb);
	report_test("Reset Function", ring_buf_is_empty(&rb));

	// 清理资源
	ring_buf_detach(&rb);
}

/* 边界条件测试 */
static void ring_buf_boundary_test(void)
{
    rt_kprintf("\n=== Ring Buffer Boundary Test ===\n");
    ring_buf_t rb;
    uint8_t buffer[TEST_BUFFER_SIZE];
    rt_size_t write_size, read_size;

    // 初始化缓冲区
    RT_ASSERT(ring_buf_init(&rb, TEST_BUFFER_SIZE) == RT_EOK);

    // 测试1: 写入刚好跨越边界
    // 半满写入
    ring_buf_put(&rb, test_data, TEST_BUFFER_SIZE / 2);

    // 读取前半部分
    ring_buf_get(&rb, buffer, TEST_BUFFER_SIZE / 4);

    // 写入跨越边界的数据
    uint8_t boundary_data = 0xAA;
    write_size = ring_buf_put(&rb, &boundary_data, 1);
    ring_buf_put(&rb, &boundary_data, 1); // 再写一次确保边界

    // 验证数据完整性和索引
    rt_bool_t boundary_ok = (rb.write_index != 0); // 更严格的检查
    ring_buf_get(&rb, buffer, 3); // 清除数据

    report_test("Boundary Write", boundary_ok);

    // 测试2: 读取跨越边界
    // 填充缓冲区
    ring_buf_put(&rb, test_data, TEST_BUFFER_SIZE);

    // 读取超过连续空间
    read_size = ring_buf_get(&rb, buffer, TEST_BUFFER_SIZE - 2);
    ring_buf_get(&rb, buffer, 3); // 跨越边界读取
    
    // 更严格的检查：读指针应该在0和缓冲区大小之间
    rt_bool_t boundary_ok2 = (rb.read_index > 0 && rb.read_index < TEST_BUFFER_SIZE);
    report_test("Boundary Read", boundary_ok2);

    // 测试3: 写满读取后的回绕
    ring_buf_reset(&rb);

    // 写入几乎满
    ring_buf_put(&rb, test_data, TEST_BUFFER_SIZE - 1);

    // 读取1字节
    uint8_t temp;
    ring_buf_get(&rb, &temp, 1);

    // 写入2字节，应成功回绕
    write_size = ring_buf_put(&rb, test_data, 2);

    // 检查写入量和缓冲区状态
    report_test("Wrap Write", write_size == 2 && ring_buf_is_full(&rb));

    // 清理资源
    ring_buf_detach(&rb);
}

/* 动态实例测试 */
static void ring_buf_dynamic_test(void)
{
	rt_kprintf("\n=== Ring Buffer Dynamic Test ===\n");

	// 创建动态实例
	ring_buf_t* rb = ring_buf_create(TEST_BUFFER_SIZE);
	report_test("Dynamic Create", rb != RT_NULL);

	// 测试基本功能
	rt_size_t write_size = ring_buf_put(rb, test_data, 8);
	rt_bool_t write_ok = (write_size == 8 && !ring_buf_is_empty(rb));

	uint8_t buffer[8];
	rt_size_t read_size = ring_buf_get(rb, buffer, 8);
	rt_bool_t read_ok = (read_size == 8 && memcmp(buffer, test_data, 8) == 0);

	report_test("Dynamic RW", write_ok && read_ok);

	// 销毁实例
	ring_buf_destroy(rb);
	report_test("Dynamic Destroy", RT_TRUE);
}

#ifdef USER_RING_BUFFER_THREAD_SAFE
/* 多线程测试数据结构 */
struct thread_test_data
{
	ring_buf_t* rb;
	rt_size_t counter;
	rt_size_t iterations;
};

/* 生产者线程 */
static void producer_thread_entry(void* parameter)
{
	struct thread_test_data* data = (struct thread_test_data*)parameter;

	for(rt_size_t i = 0; i < data->iterations; i++)
	{
		rt_size_t write_size = ring_buf_put(data->rb, test_data, sizeof(test_data));
		if(write_size != sizeof(test_data))
		{
			rt_kprintf("Producer write error: %d\n", write_size);
		}

		data->counter++;
		rt_thread_mdelay(5); // 模拟工作负载
	}
}

/* 消费者线程 */
static void consumer_thread_entry(void* parameter)
{
	struct thread_test_data* data = (struct thread_test_data*)parameter;
	uint8_t buffer[TEST_BUFFER_SIZE];

	for(rt_size_t i = 0; i < data->iterations; i++)
	{
		rt_size_t read_size = ring_buf_get(data->rb, buffer, sizeof(buffer));
		if(read_size != sizeof(buffer))
		{
			rt_kprintf("Consumer read error: %d\n", read_size);
		}

		// 验证数据完整性
		if(memcmp(buffer, test_data, sizeof(test_data)) != 0)
		{
			rt_kprintf("Consumer data corruption!\n");
		}

		data->counter++;
		rt_thread_mdelay(7); // 模拟工作负载
	}
}

/* 多线程压力测试 */
static void ring_buf_thread_safety_test(void)
{
	rt_kprintf("\n=== Ring Buffer Thread Safety Test ===\n");

	// 创建缓冲区
	ring_buf_t* rb = ring_buf_create(TEST_BUFFER_SIZE);
	RT_ASSERT(rb != RT_NULL);

	// 准备测试数据
	const rt_size_t iterations = 100;
	struct thread_test_data producer_data = {rb, 0, iterations};
	struct thread_test_data consumer_data = {rb, 0, iterations};

	// 创建生产者和消费者线程
	struct rt_thread producer;
	rt_thread_init(&producer, "producer",
	               producer_thread_entry,
	               &producer_data,
	               producer_buffer,
	               THREAD_STACK_SIZE,
	               THREAD_PRIORITY,
	               THREAD_TIMESLICE);

	struct rt_thread consumer;
	rt_thread_init(&consumer, "consumer",
	               consumer_thread_entry,
	               &consumer_data,
	               consumer_buffer,
	               THREAD_STACK_SIZE,
	               THREAD_PRIORITY,
	               THREAD_TIMESLICE);

	// 启动线程
	RT_ASSERT(rt_thread_startup(&producer) == RT_EOK);
	RT_ASSERT(rt_thread_startup(&consumer) == RT_EOK);

	// 等待线程完成
	rt_thread_mdelay(iterations * 10); // 预估时间

	// 检查结果
	rt_bool_t threads_ok = (producer_data.counter == iterations &&
	                        consumer_data.counter == iterations &&
	                        ring_buf_is_empty(rb));

	report_test("Thread Completion", threads_ok);
	report_test("Buffer State", ring_buf_is_empty(rb));

	// 清理资源
	ring_buf_destroy(rb);
	rt_thread_delete(&producer);
	rt_thread_delete(&consumer);
}
#endif /* USER_RING_BUFFER_THREAD_SAFE */

/* 主测试函数 */
void ring_buffer_test(void)
{
	rt_kprintf("\n***** Starting Ring Buffer Test Suite *****\n");

	// 执行测试用例
	ring_buf_basic_test();
	ring_buf_boundary_test();
	ring_buf_dynamic_test();

#ifdef USER_RING_BUFFER_THREAD_SAFE
	ring_buf_thread_safety_test();
#endif

	rt_kprintf("\n***** Ring Buffer Test Complete *****\n");
}
//MSH_CMD_EXPORT(ring_buffer_test, Run ring buffer test suite);
/* Public functions --------------------------------------------------------- */

#ifdef __cplusplus
}
#endif
// <<< end of configuration section >>>
/* ----------------------------- end of ring_buffer_example.c ---------------------------- */